package com.topisv.tms.utils;

import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Dictionary;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.UUID;

import org.apache.commons.beanutils.PropertyUtils;
import org.springframework.util.StringUtils;

/**
 * 共通工具类
 * @author wucx
 * 
 */
public class PubUtil {
    
    /**
     * 四舍五入保留两位小数
     * @return
     * @author:Fisher
     * @email:zhuangcaijin@126.com
     */
    public static BigDecimal conversionTowDecimal(BigDecimal value) {
        value =  value.setScale(2, BigDecimal.ROUND_HALF_UP);
        return value;
    }
    
    /**
     * 生成UUID
     * @return UUID
     */
    public static String getUUID() {
        return UUID.randomUUID().toString().replaceAll("-", "");
    }
    
	/**
	 * 检查传入的参数是否为空。
	 * @return boolean 如果被检查值为null，返回true。 
	 * 如果value的类型为String，并且value.length()为0，返回true。
	 * 如果value的类型为Object[]，并且value.length为0，返回true。
	 * 如果value的类型为Collection，并且value.size()为0，返回true。
	 * 如果value的类型为Dictionary，并且value.size()为0，返回true。 
	 * 如果value的类型为Map，并且value.size()为0，返回true。 
	 * 否则返回false。
	 * @param value
	 *            被检查值。
	 */
	public static boolean isEmpty(Object value) {
		if (value == null){
			return true;
		}
		if ((value instanceof String) && (((String) value).trim().length() <= 0)){
			return true;
		}
        if ((value instanceof Object[]) && (((Object[]) value).length <= 0)) {
            return true;
        }
        //判断数组中的值是否全部为空null.
		if (value instanceof Object[]) {
            Object[] t = (Object[]) value;
            for (int i = 0; i < t.length; i++) {
                if (t[i] != null) {
                    return false;
                }
            }
            return true;
        }
		if ((value instanceof Collection) && ((Collection) value).size() <= 0){
			return true;
		}
		if ((value instanceof Dictionary) && ((Dictionary) value).size() <= 0){
			return true;
		}
		if ((value instanceof Map) && ((Map) value).size() <= 0){
			return true;
		}
		return false;
	}
	
	public static boolean isNotEmpty(Object value) {
		return !PubUtil.isEmpty(value);
	}

    /**
     * map按key值复值value到类属性
     * @param from
     * @param to
     * @throws Exception
     */
    public static void copyProperties(Map from, Object to) {
    	if (PubUtil.isEmpty(from))
    		return;
    	
    	if (PubUtil.isEmpty(to))
    		throw new RuntimeException("targe object is null");
    	
        Iterator entries = ((Map) from).entrySet().iterator();
        while (entries.hasNext()) {
            Map.Entry entry = (Map.Entry) entries.next();
            String name = getPropertyNameByKey(entry.getKey().toString().toLowerCase(), "_");
            try {
                //oracle
                if(name.equals("rownum")){
                    continue;
                }
				PropertyUtils.setSimpleProperty(to, name, entry.getValue());
			} catch (IllegalAccessException e) {
				throw new RuntimeException(e.getMessage(), e);
			} catch (InvocationTargetException e) {
				throw new RuntimeException(e.getMessage(), e);
			} catch (NoSuchMethodException e) {
				throw new RuntimeException(e.getMessage(), e);
			}
        }

    }
    
    /**
     * 把Map转换成对像(按key->property)
     * @param listMap
     * @param targetCLZ
     * @return
     * @throws Exception 
     */
    @SuppressWarnings("unchecked")
	public static List convertListMapToObject(List<Map> from, Class targetCLZ) {
    	if (PubUtil.isEmpty(from))
    		return null;
    	
    	List resultList = new ArrayList();
    	for (Map map : from) {
    		Object targetInst = null;
			try {
				targetInst = targetCLZ.newInstance();
				copyProperties(map, targetInst);
			} catch (InstantiationException e) {
				e.printStackTrace();
			} catch (IllegalAccessException e) {
				e.printStackTrace();
			}
			
			resultList.add(targetInst);
		}
    	
    	return resultList;
    }
    
    /**
     * 对象转map
     * @param obj
     * @return Map Map
     */
    @SuppressWarnings("rawtypes")
    public static Map ConvertObjToMap(Object obj){
        Map<String,Object> reMap = new HashMap<String,Object>();
        if (obj == null) 
            return null;
        Field[] fields = obj.getClass().getDeclaredFields();
        try {
            for(int i=0;i<fields.length;i++){
                try {
                    Field f = obj.getClass().getDeclaredField(fields[i].getName());
                    f.setAccessible(true);
                    Object o = f.get(obj);
                    reMap.put(fields[i].getName(), o);
                } catch (NoSuchFieldException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                } catch (IllegalArgumentException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                } catch (IllegalAccessException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }
            }
        } catch (SecurityException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } 
        return reMap;
    }
    
    /**
     * 把key转换属性名(删除split字符，split后第一个字符变成大写)
     * @param key
     * @param split
     * @return
     */
    public static String getPropertyNameByKey(String key, String split){
    	if (PubUtil.isEmpty(key))
    		return null;
    	
    	if (key.indexOf(split)<=0)
    		return key;
    	
    	String[] keys = key.split(split);
    	String result = "";
    	for (int i = 0; i < keys.length; i++) {
    		if (i>0){
    			keys[i] = keys[i].substring(0, 1).toUpperCase() + keys[i].substring(1);
    		}
    		result = result + keys[i];
		}
    	
    	return result;
    }
    
	/**
	 * 将字符串数组(List)的元素以指定连接符unionChar拼接成字符串，每个数组元素前后都将添加appendChar。
	 * 
	 * <p>
	 * <strong>用例描述：</strong>
	 * 
	 * <pre>
	 * getUnionStr(new String[] { &quot;A&quot;, &quot;B&quot;, &quot;C&quot; }, &quot;,&quot;, &quot;&quot;) = &quot;A,B,C&quot;;
	 * getUnionStr(new String[] { &quot;A&quot;, &quot;B&quot;, &quot;C&quot; }, &quot;,&quot;, &quot;*&quot;) = &quot;*A*,*B*,*C*&quot;;
	 * </pre>
	 * 
	 * @params strAry 用于连接的字符串数组
	 * @params unionChar 用来连接的中间字符
	 * @params appendChar 用来在每个字符中追加
	 */
	public static String getUnionString(Collection<String> strCols, String unionChar,String appendChar) {
		if (PubUtil.isEmpty(strCols))
			return null;
		
		StringBuffer ret = new StringBuffer();
		int i=0;
		for (String str : strCols) {
			if (i != 0)
				ret.append(unionChar);
			ret.append(appendChar + str + appendChar);
			i++;
		}
		
		return ret.toString();
	}
	
	
	public static String filterNULL(Object target) {
        if (isNotEmpty(target)) {
            return target.toString();
        } else {
            return "";
        }
    }

    public static String filterNULLSPACE(Object target) {
        if (isNotEmpty(target)) {
            return StringUtils.trimWhitespace(target.toString());
        } else {
            return "";
        }
    }

    public static String filterNULLAllSPACE(Object target) {
        if (isNotEmpty(target)) {
            return StringUtils.trimAllWhitespace(target.toString());
        } else {
            return "";
        }
    }

}
